﻿using System;
using System.Collections.Generic;
using UnityEngine;

namespace Z1029.NoteGlobalView
{
    public class JudgementLine : MonoBehaviour
    {
        public float speed, alpha;
        public SpeedEvent[] speeds;
        public List<ValueSet> moveEvents;
        public List<ValueSet> rotateEvents;
        public List<ValueSet> alphaEvents;
        public float bpm;
        public Color AP, FC;
        public SpriteRenderer lineShow;
        public float[] positionX;
        public List<Note> nearJudgeNotes;
        public SpriteRenderer select;
        public TextMesh indexShow;
        public int index;

        public bool IsSelect => selectedJudgeline == this;

        public static JudgementLine selectedJudgeline;
        public static bool IsEditing;

        private void Start()
        {
            indexShow.text = index.ToString();
            transform.localPosition = Vector3.zero;
            indexShow.GetComponent<Renderer>().sortingLayerID = lineShow.sortingLayerID;
            indexShow.GetComponent<Renderer>().sortingOrder = 3000;
        }

        private void Update()
        {
            UpdateJudgelinePosition();
            UpdateJudgelineRotation();
            UpdateJudgelineColor();
            UpdateSpeed();
            transform.localScale = Vector3.one;
        }

        public void UpdateSpeed()
        {
            speed = GetSpeed(LevelController.nowTime);
        }

        public float GetSpeed(double time)
        {
            for (int i = 0; i < speeds.Length; i++)
            {
                float? value = Utils.GetValueFromTimeAndValue(time, speeds[i].startTime, speeds[i].endTime, speeds[i].value, speeds[i].value);
                if (value != null)
                {
                    return (float)value;
                }
            }
            return 0;
        }

        public void UpdateJudgelinePosition()
        {
            Vector3 targetPos = transform.localPosition;
            for (int i = 0; i < moveEvents.Count; i++)
            {
                float startT = moveEvents[i].startTime;
                float endT = moveEvents[i].endTime;
                float vs = moveEvents[i].start;
                float ve = moveEvents[i].end;
                float vs2 = moveEvents[i].start2;
                float ve2 = moveEvents[i].end2;
                float? x = Utils.GetValueFromTimeAndValue(LevelController.nowTime, startT, endT, vs, ve);
                float? y = Utils.GetValueFromTimeAndValue(LevelController.nowTime, startT, endT, vs2, ve2);
                if (x != null)
                {
                    targetPos.x = (float)x;
                    targetPos.y = (float)y;
                }
            }
            transform.localPosition = targetPos;
        }

        public void UpdateJudgelineRotation()
        {
            Vector3 targetRot = transform.localEulerAngles;
            for (int i = 0; i < rotateEvents.Count; i++)
            {
                float startT = rotateEvents[i].startTime;
                float endT = rotateEvents[i].endTime;
                float vs = rotateEvents[i].start;
                float ve = rotateEvents[i].end;
                float? z = Utils.GetValueFromTimeAndValue(LevelController.nowTime, startT, endT, vs, ve);
                //float? y = Utils.GetValueFromTimeAndValue(LevelController.nowTime, startT, endT, vs2, ve2);
                if (z != null)
                {
                    targetRot.z = (float)z;
                }
            }
            transform.localEulerAngles = targetRot;
        }

        public void UpdateJudgelineColor()
        {
            for (int i = 0; i < alphaEvents.Count; i++)
            {
                float startT = alphaEvents[i].startTime;
                float endT = alphaEvents[i].endTime;
                float vs = alphaEvents[i].start;
                float ve = alphaEvents[i].end;
                float? value = Utils.GetValueFromTimeAndValue(LevelController.nowTime, startT, endT, vs, ve);
                if (value != null) alpha = (float)value;
            }
            Color color = alpha < 0.05f ? Color.black:Color.white;
            color.a = alpha<0.05f?0.1f:alpha;
            if (IsSelect)
            {
                color = Color.red;
                select.color = Color.red;
            }
            else
            {
                Color colorc = (Color.red + Color.white)/2;
                select.color = colorc;
            }
            lineShow.color = color;

            if(Input.GetKeyDown(KeyCode.Return) && IsSelect && !IsEditing)
            {
                //NoteEditor.LevelController.chart = ConvertToNEJson();
                UnityEngine.SceneManagement.SceneManager.LoadScene("MainEditor",UnityEngine.SceneManagement.LoadSceneMode.Additive);
            }
        }

        public double GetSpeedDistance(double time)
        {
            double num = 0;
            int index = speeds.Length - 1;
            for (int i = 0; i < speeds.Length; i++)
            {
                float start = speeds[i].startTime;
                float end = speeds[i].endTime;
                float value = speeds[i].value;
                if (start > time)
                {
                    index = i - 1;
                    break;
                }
                if (end > LevelController.nowTime)
                {
                    if (start < LevelController.nowTime)
                        num += (end - LevelController.nowTime) * value;
                    else num += (end - start) * value;
                }
            }
            num -= (speeds[index].endTime - time) * speeds[index].value;
            num /= 2;
            return num;
        }

        private void OnMouseDown()
        {
            if (!IsEditing)
                selectedJudgeline = this;
        }
    }
}